home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1997 January: Mac OS SDK / Dev.CD Jan 97 SDK2.toast / Development Kits (Disc 2) / OpenDoc Development Framework / ODFDev / ODF / Framewrk / FWSemEvt / FWScptbl.cpp < prev    next >
Encoding:
Text File  |  1996-09-17  |  36.5 KB  |  1,315 lines  |  [TEXT/MPS ]

  1. //========================================================================================
  2. //
  3. //    File:                FWSemObj.cpp
  4. //    Release Version:    $ ODF 2 $
  5. //
  6. //    Copyright:    (c) 1993 - 1996 by Apple Computer, Inc., all rights reserved.
  7. //
  8. //========================================================================================
  9.  
  10. #ifndef FWSCPTBL_H
  11. #include "FWScptbl.h"
  12. #endif
  13.  
  14. #ifndef FWACQSCR_H
  15. #include "FWAcqScr.h"
  16. #endif
  17.  
  18. #ifndef FWPART_H
  19. #include "FWPart.h"
  20. #endif
  21.  
  22. #ifndef FWSCPCOL_H
  23. #include "FWScpCol.h"
  24. #endif
  25.  
  26. #ifndef FWSEMINT_H
  27. #include "FWSemInt.h"
  28. #endif
  29.  
  30. #ifndef FWAPLEVT_H
  31. #include "FWAplEvt.h"
  32. #endif
  33.  
  34. #ifndef FWDSCOPR_H
  35. #include "FWDscOpr.h"
  36. #endif
  37.  
  38. #ifndef FWOBJSPC_H
  39. #include "FWObjSpc.h"
  40. #endif
  41.  
  42. #ifndef FWSCPPRP_H
  43. #include "FWScpPrp.h"
  44. #endif
  45.  
  46. // ----- OS Layer -----
  47.  
  48. #ifndef SLODFSTR_K
  49. #include "SLODFStr.k"
  50. #endif
  51.  
  52. #ifndef SLODFSTR_H
  53. #include "SLODFStr.h"
  54. #endif
  55.  
  56. #ifndef __AEOBJECTS__
  57. #include <AEObjects.h>
  58. #endif
  59.  
  60. #ifndef __AEPACKOBJECT__
  61. #include <AEPackObject.h>
  62. #endif
  63.  
  64. //========================================================================================
  65. //    Runtime Information
  66. //========================================================================================
  67.  
  68. #ifdef FW_BUILD_MAC    
  69. #pragma segment fwsemevt
  70. #endif
  71.  
  72. //========================================================================================
  73. //    Template Instantiations
  74. //========================================================================================
  75.  
  76. FW_DEFINE_AUTO_TEMPLATE(FW_TOrderedCollection, FW_MScriptable)
  77. FW_DEFINE_AUTO_TEMPLATE(FW_TOrderedCollectionIterator, FW_MScriptable)
  78.  
  79. #ifdef FW_USE_TEMPLATE_PRAGMAS
  80.  
  81. #pragma template_access public
  82. #pragma template FW_TOrderedCollection<FW_MScriptable>
  83. #pragma template FW_TOrderedCollectionIterator<FW_MScriptable>
  84.  
  85. #endif
  86.  
  87. FW_DEFINE_AUTO(FW_MScriptable)
  88. FW_DEFINE_AUTO(FW_CElementIterator)
  89.  
  90. //========================================================================================
  91. //    class FW_MScriptable
  92. //========================================================================================
  93.  
  94. FW_DEFINE_CLASS_M0(FW_MScriptable)
  95.  
  96. //---------------------------------------------------------------------------------------
  97. //    FW_MScriptable::FW_MScriptable
  98. //---------------------------------------------------------------------------------------
  99.  
  100. FW_MScriptable::FW_MScriptable() :
  101.     fDependents(NULL)
  102. {
  103.     FW_END_CONSTRUCTOR
  104. }
  105.  
  106. //---------------------------------------------------------------------------------------
  107. //    FW_MScriptable::~FW_MScriptable
  108. //---------------------------------------------------------------------------------------
  109.  
  110. FW_MScriptable::~FW_MScriptable()
  111. {
  112.     FW_START_DESTRUCTOR
  113.     
  114.     if (fDependents)
  115.     {
  116.         FW_TOrderedCollectionIterator<FW_MScriptable> iter(fDependents);
  117.         for (FW_MScriptable* i = iter.First(); iter.IsNotComplete(); i = iter.Next())
  118.         {
  119.             i->HandlePrimaryDeleted(this);
  120.         }
  121.         delete fDependents;
  122.     }
  123. }
  124.  
  125. //---------------------------------------------------------------------------------------
  126. //    FW_MScriptable::GetObjectClass
  127. //---------------------------------------------------------------------------------------
  128.  
  129. ODDescType FW_MScriptable::GetObjectClass() const
  130. {
  131.     return cObject;
  132. }
  133.  
  134. //---------------------------------------------------------------------------------------
  135. //    FW_MScriptable::GetSpecifierForm
  136. //---------------------------------------------------------------------------------------
  137.  
  138. ODDescType FW_MScriptable::GetSpecifierForm() const
  139. {
  140.     return formAbsolutePosition;
  141. }
  142.  
  143. //---------------------------------------------------------------------------------------
  144. //    FW_MScriptable::HandleSemanticEvent
  145. //---------------------------------------------------------------------------------------
  146.  
  147. void FW_MScriptable::HandleSemanticEvent(Environment* ev,
  148.                                         FW_CPart* part,
  149.                                         AEKeyword eventClass,
  150.                                         AEKeyword eventID,
  151.                                         const FW_CAppleEvent& event,
  152.                                         FW_CAppleEvent& reply)
  153. {
  154.     if (eventClass == kAECoreSuite)
  155.     {
  156.         switch (eventID)
  157.         {
  158.             case kAEClone:
  159.                 DoAEClone(ev, part, event, reply);
  160.                 break;
  161.             
  162.             case kAEClose:
  163.                 DoAEClose(ev, part, event, reply);
  164.                 break;
  165.                 
  166.             case kAECountElements:
  167.                 DoAECountElements(ev, part, event, reply);
  168.                 break;
  169.                 
  170.             case kAECreateElement:
  171.                 DoAECreateElement(ev, part, event, reply);
  172.                 break;
  173.                 
  174.             case kAEDelete:
  175.                 DoAEDelete(ev, part, event, reply);
  176.                 break;
  177.                 
  178.             case kAEDoObjectsExist:
  179.                 DoAEDoObjectsExist(ev, part, event, reply);
  180.                 break;
  181.                 
  182.             case kAEGetClassInfo:
  183.                 DoAEGetClassInfo(ev, part, event, reply);
  184.                 break;
  185.                 
  186.             case kAEGetData:
  187.                 DoAEGetData(ev, part, event, reply);
  188.                 break;
  189.             
  190.             case kAEGetDataSize:
  191.                 DoAEGetDataSize(ev, part, event, reply);
  192.                 break;
  193.                 
  194.             case kAEGetEventInfo:
  195.                 DoAEGetEventInfo(ev, part, event, reply);
  196.                 break;
  197.                 
  198.             case kAEMove:
  199.                 DoAEMove(ev, part, event, reply);
  200.                 break;
  201.                                 
  202.             case kAEOpen:
  203.                 DoAEOpen(ev, part, event, reply);
  204.                 break;
  205.                 
  206.             case kAEPrint:
  207.                 DoAEPrint(ev, part, event, reply);
  208.                 break;
  209.                 
  210.             case kAESave:
  211.                 DoAESave(ev, part, event, reply);
  212.                 break;
  213.                 
  214.             case kAESetData:
  215.                 DoAESetData(ev, part, event, reply);
  216.                 break;
  217.  
  218.             default:
  219.                 DoSemanticEvent(ev, part, eventClass, eventID, event, reply);
  220.                 break;
  221.         }
  222.     }
  223.     else
  224.         DoSemanticEvent(ev, part, eventClass, eventID, event, reply);
  225. }
  226.  
  227. //---------------------------------------------------------------------------------------
  228. //    FW_MScriptable::DoSemanticEvent
  229. //---------------------------------------------------------------------------------------
  230.  
  231. void FW_MScriptable::DoSemanticEvent(Environment* ev,
  232.                                     FW_CPart* part,
  233.                                     AEKeyword eventClass,
  234.                                     AEKeyword eventID,
  235.                                     const FW_CAppleEvent& event,
  236.                                     FW_CAppleEvent& reply)
  237. {
  238. FW_UNUSED(ev);
  239. FW_UNUSED(part);
  240. FW_UNUSED(eventClass);
  241. FW_UNUSED(eventID);
  242. FW_UNUSED(event);
  243. FW_UNUSED(reply);
  244.     FW_Failure(errAEEventNotHandled);
  245. }
  246.  
  247. //---------------------------------------------------------------------------------------
  248. //    FW_MScriptable::DoAEClone
  249. //---------------------------------------------------------------------------------------
  250.  
  251. void FW_MScriptable::DoAEClone(Environment* ev,
  252.                             FW_CPart* part,
  253.                             const FW_CAppleEvent& event,
  254.                             FW_CAppleEvent& reply)
  255. {
  256. FW_UNUSED(ev);
  257. FW_UNUSED(part);
  258. FW_UNUSED(event);
  259. FW_UNUSED(reply);
  260.     FW_Failure(errAEEventNotHandled);
  261. }
  262.  
  263. //---------------------------------------------------------------------------------------
  264. //    FW_MScriptable::DoAEClose
  265. //---------------------------------------------------------------------------------------
  266.  
  267. void FW_MScriptable::DoAEClose(Environment* ev,
  268.                             FW_CPart* part,
  269.                             const FW_CAppleEvent& event,
  270.                             FW_CAppleEvent& reply)
  271. {
  272. FW_UNUSED(ev);
  273. FW_UNUSED(part);
  274. FW_UNUSED(event);
  275. FW_UNUSED(reply);
  276.     FW_Failure(errAEEventNotHandled);
  277. }
  278.  
  279. //---------------------------------------------------------------------------------------
  280. //    FW_MScriptable::DoAECountElements
  281. //---------------------------------------------------------------------------------------
  282.  
  283. void FW_MScriptable::DoAECountElements(Environment* ev,
  284.                                         FW_CPart* part,
  285.                                         const FW_CAppleEvent& event,
  286.                                         FW_CAppleEvent& reply)
  287. {
  288.     reply.PutLongInteger(CountElements(ev, part, event.GetType(keyAEObjectClass)), keyAEResult);
  289. }
  290.  
  291. //---------------------------------------------------------------------------------------
  292. //    FW_MScriptable::DoAECreate
  293. //---------------------------------------------------------------------------------------
  294.  
  295. void FW_MScriptable::DoAECreateElement(Environment* ev,
  296.                                         FW_CPart* part,
  297.                                         const FW_CAppleEvent& event,
  298.                                         FW_CAppleEvent& reply)
  299. {
  300. FW_UNUSED(ev);
  301. FW_UNUSED(part);
  302. FW_UNUSED(event);
  303. FW_UNUSED(reply);
  304.     FW_Failure(errAEEventNotHandled);
  305. }
  306.  
  307. //---------------------------------------------------------------------------------------
  308. //    FW_MScriptable::DoAEDelete
  309. //---------------------------------------------------------------------------------------
  310.  
  311. void FW_MScriptable::DoAEDelete(Environment* ev,
  312.                                 FW_CPart* part,
  313.                                 const FW_CAppleEvent& event,
  314.                                 FW_CAppleEvent& reply)
  315. {
  316. FW_UNUSED(ev);
  317. FW_UNUSED(part);
  318. FW_UNUSED(event);
  319. FW_UNUSED(reply);
  320.     FW_Failure(errAEEventNotHandled);
  321. }
  322.  
  323. //---------------------------------------------------------------------------------------
  324. //    FW_MScriptable::DoAEDoObjectsExist
  325. //---------------------------------------------------------------------------------------
  326.  
  327. void FW_MScriptable::DoAEDoObjectsExist(Environment* ev,
  328.                                         FW_CPart* part,
  329.                                         const FW_CAppleEvent& event,
  330.                                         FW_CAppleEvent& reply)
  331. {
  332. FW_UNUSED(ev);
  333. FW_UNUSED(part);
  334. FW_UNUSED(event);
  335. FW_UNUSED(reply);
  336.     FW_Failure(errAEEventNotHandled);
  337. }
  338.  
  339. //---------------------------------------------------------------------------------------
  340. //    FW_MScriptable::DoAEGetClassInfo
  341. //---------------------------------------------------------------------------------------
  342.  
  343. void FW_MScriptable::DoAEGetClassInfo(Environment* ev,
  344.                                     FW_CPart* part,
  345.                                     const FW_CAppleEvent& event,
  346.                                     FW_CAppleEvent& reply)
  347. {
  348. FW_UNUSED(ev);
  349. FW_UNUSED(part);
  350. FW_UNUSED(event);
  351. FW_UNUSED(reply);
  352.     FW_Failure(errAEEventNotHandled);
  353. }
  354.  
  355. //---------------------------------------------------------------------------------------
  356. //    FW_MScriptable::DoAEGetData
  357. //---------------------------------------------------------------------------------------
  358.  
  359. void FW_MScriptable::DoAEGetData(Environment* ev,
  360.                                 FW_CPart* part,
  361.                                 const FW_CAppleEvent& event,
  362.                                 FW_CAppleEvent& reply)
  363. {
  364. FW_UNUSED(event);
  365.     FW_CDesc objectSpecifier;
  366.     
  367.     BuildObjectSpecifier(ev, part, GetFrame(ev, part), objectSpecifier, GetSpecifierForm());
  368.     reply.PutDataByDesc(objectSpecifier, keyAEResult);
  369. }
  370.  
  371. //---------------------------------------------------------------------------------------
  372. //    FW_MScriptable::DoAEGetDataSize
  373. //---------------------------------------------------------------------------------------
  374.  
  375. void FW_MScriptable::DoAEGetDataSize(Environment* ev,
  376.                                     FW_CPart* part,
  377.                                     const FW_CAppleEvent& event,
  378.                                     FW_CAppleEvent& reply)
  379. {
  380. FW_UNUSED(ev);
  381. FW_UNUSED(part);
  382. FW_UNUSED(event);
  383. FW_UNUSED(reply);
  384.     FW_Failure(errAEEventNotHandled);
  385. }
  386.  
  387. //---------------------------------------------------------------------------------------
  388. //    FW_MScriptable::DoAEGetEventInfo
  389. //---------------------------------------------------------------------------------------
  390.  
  391. void FW_MScriptable::DoAEGetEventInfo(Environment* ev,
  392.                                     FW_CPart* part,
  393.                                     const FW_CAppleEvent& event,
  394.                                     FW_CAppleEvent& reply)
  395. {
  396. FW_UNUSED(ev);
  397. FW_UNUSED(part);
  398. FW_UNUSED(event);
  399. FW_UNUSED(reply);
  400.     FW_Failure(errAEEventNotHandled);
  401. }
  402.  
  403. //---------------------------------------------------------------------------------------
  404. //    FW_MScriptable::DoAEMove
  405. //---------------------------------------------------------------------------------------
  406.  
  407. void FW_MScriptable::DoAEMove(Environment* ev,
  408.                             FW_CPart* part,
  409.                             const FW_CAppleEvent& event,
  410.                             FW_CAppleEvent& reply)
  411. {
  412. FW_UNUSED(ev);
  413. FW_UNUSED(part);
  414. FW_UNUSED(event);
  415. FW_UNUSED(reply);
  416.     FW_Failure(errAEEventNotHandled);
  417. }
  418.  
  419. //---------------------------------------------------------------------------------------
  420. //    FW_MScriptable::DoAEOpen
  421. //---------------------------------------------------------------------------------------
  422.  
  423. void FW_MScriptable::DoAEOpen(Environment* ev,
  424.                             FW_CPart* part,
  425.                             const FW_CAppleEvent& event,
  426.                             FW_CAppleEvent& reply)
  427. {
  428. FW_UNUSED(ev);
  429. FW_UNUSED(part);
  430. FW_UNUSED(event);
  431. FW_UNUSED(reply);
  432.     FW_Failure(errAEEventNotHandled);
  433. }
  434.  
  435. //---------------------------------------------------------------------------------------
  436. //    FW_MScriptable::DoAEPrint
  437. //---------------------------------------------------------------------------------------
  438.  
  439. void FW_MScriptable::DoAEPrint(Environment* ev,
  440.                             FW_CPart* part,
  441.                             const FW_CAppleEvent& event,
  442.                             FW_CAppleEvent& reply)
  443. {
  444. FW_UNUSED(ev);
  445. FW_UNUSED(part);
  446. FW_UNUSED(event);
  447. FW_UNUSED(reply);
  448.     FW_Failure(errAEEventNotHandled);
  449. }
  450.  
  451. //---------------------------------------------------------------------------------------
  452. //    FW_MScriptable::DoAESave
  453. //---------------------------------------------------------------------------------------
  454.  
  455. void FW_MScriptable::DoAESave(Environment* ev,
  456.                             FW_CPart* part,
  457.                             const FW_CAppleEvent& event,
  458.                             FW_CAppleEvent& reply)
  459. {
  460. FW_UNUSED(ev);
  461. FW_UNUSED(part);
  462. FW_UNUSED(event);
  463. FW_UNUSED(reply);
  464.     FW_Failure(errAEEventNotHandled);
  465. }
  466.  
  467. //---------------------------------------------------------------------------------------
  468. //    FW_MScriptable::DoAESetData
  469. //---------------------------------------------------------------------------------------
  470.  
  471. void FW_MScriptable::DoAESetData(Environment* ev,    
  472.                                 FW_CPart* part,
  473.                                 const FW_CAppleEvent& event,
  474.                                 FW_CAppleEvent& reply)
  475. {
  476. FW_UNUSED(ev);
  477. FW_UNUSED(part);
  478. FW_UNUSED(event);
  479. FW_UNUSED(reply);
  480.     FW_Failure(errAEEventNotHandled);
  481. }
  482.  
  483. //---------------------------------------------------------------------------------------
  484. //    FW_MScriptable::GetFrame
  485. //---------------------------------------------------------------------------------------
  486.  
  487. FW_CFrame* FW_MScriptable::GetFrame(Environment* ev, FW_CPart* part) const
  488. {
  489.     return (part->GetLastActiveFrame(ev));
  490. }
  491.  
  492. //---------------------------------------------------------------------------------------
  493. //    FW_MScriptable::CompareScriptableObjects
  494. //---------------------------------------------------------------------------------------
  495.  
  496. FW_Boolean FW_MScriptable::CompareScriptableObjects(Environment* ev,
  497.                                                     FW_CPart* part,
  498.                                                     ODDescType operation,
  499.                                                     const FW_CDesc& other) const
  500. {
  501. FW_UNUSED(ev);
  502. FW_UNUSED(part);
  503.     FW_Boolean result = FALSE;
  504.     
  505.     if ((operation == kAEEquals) && (other.DescriptorType() == FW_kSemanticObjectTokenType))
  506.     {
  507.         FW_MScriptable* otherObject = ::FW_ExtractScriptableFromDesc(other);
  508.         result = (this == otherObject);
  509.     }
  510.     
  511.     return result;
  512. }
  513.  
  514. //---------------------------------------------------------------------------------------
  515. //    FW_MScriptable::AcquireContainingObject
  516. //---------------------------------------------------------------------------------------
  517.  
  518. FW_MScriptable* FW_MScriptable::AcquireContainingObject(Environment* ev,
  519.                                                         FW_CPart* part) const
  520. {
  521. FW_UNUSED(ev);
  522.         // default implementation is to return the part as the container.
  523.         // in the case of multiple levels of containment, this method
  524.         // should be overridden and the correct container should be returned
  525.     FW_MScriptable* containingObject = FW_DYNAMIC_CAST(FW_MScriptable, part);
  526.     FW_ASSERT(containingObject != NULL);
  527.     
  528.     containingObject->AcquireScriptable();
  529.     return containingObject;
  530. }
  531.  
  532. //---------------------------------------------------------------------------------------
  533. //    FW_MScriptable::AcquireContainedObject
  534. //---------------------------------------------------------------------------------------
  535.  
  536. FW_MScriptable* FW_MScriptable::AcquireContainedObject(Environment* ev,
  537.                                                     FW_CPart* part,
  538.                                                     ODDescType desiredClass,
  539.                                                     ODDescType form,
  540.                                                     const FW_CDesc& selectionData)
  541. {
  542.     FW_MScriptable* acquiredObject = NULL;
  543.         
  544.     if (desiredClass == cProperty)
  545.     {
  546.         ODDescType whichProperty;
  547.         selectionData >> whichProperty;
  548.         
  549.         if (HasProperty(whichProperty))
  550.             acquiredObject = FW_NEW(FW_CPropertyDesignator, (part, this, whichProperty));
  551.     }
  552.     else
  553.     {
  554.         switch (form)
  555.         {
  556.             case formName:
  557.                 {
  558.                     FW_CString desiredName;
  559.                     selectionData.GetString(desiredName);
  560.                     acquiredObject = AcquireElementByName(ev, part, desiredClass, desiredName);
  561.                 }
  562.                 break;
  563.             
  564.             case formRelativePosition:
  565.                 {
  566.                     ODDescType relativePosition;
  567.                     
  568.                     relativePosition = selectionData.GetEnumeratedType();
  569.                     acquiredObject = AcquireAdjacentObject(ev, part, desiredClass, relativePosition);
  570.                 }
  571.                 break;
  572.             
  573.             case formRange:
  574.                 {
  575.                     FW_CAcquiredScriptable startObject;
  576.                     FW_CAcquiredScriptable stopObject;
  577.                     
  578.                     FW_CSemanticInterface* semInt = part->GetSemanticInterface(ev);
  579.                     
  580.                     FW_ASSERT(semInt);
  581.                     
  582.                     FW_CDesc rangeRecord;
  583.                     FW_CDesc objectSpec;
  584.                     FW_CDesc objectToken;
  585.                     
  586.                     selectionData.Coerce(typeAERecord, rangeRecord);
  587.     
  588.                     rangeRecord.GetDataByDesc(objectSpec, keyAERangeStart);
  589.                     semInt->Resolve(ev, objectSpec, objectToken);
  590.                     startObject = semInt->AcquireScriptableFromToken(ev, objectToken);
  591.                     
  592.                     objectSpec.Clear();
  593.                     objectToken.Clear();
  594.                     
  595.                     rangeRecord.GetDataByDesc(objectSpec, keyAERangeStop);
  596.                     semInt->Resolve(ev, objectSpec, objectToken);
  597.                     stopObject = semInt->AcquireScriptableFromToken(ev, objectToken);
  598.                     
  599.                     acquiredObject = AcquireElementsWithinRange(ev, part, desiredClass, startObject, stopObject);
  600.                 }
  601.                 break;
  602.             
  603.             case formUniqueID:
  604.                 break;
  605.                 
  606.             case formAbsolutePosition:
  607.                     // should verify that element the desiredClass supports pIndex
  608.                     acquiredObject = AcquireElementByAbsolutePosition(ev, part, desiredClass, selectionData);
  609.                 break;
  610.                 
  611.             default:
  612.                 break;
  613.         }
  614.     }
  615.     return acquiredObject;
  616. }
  617.  
  618. //---------------------------------------------------------------------------------------
  619. //    FW_MScriptable::AcquireElementByAbsolutePosition
  620. //---------------------------------------------------------------------------------------
  621.  
  622. FW_MScriptable* FW_MScriptable::AcquireElementByAbsolutePosition(Environment* ev,
  623.                                                                 FW_CPart* part,
  624.                                                                 ODDescType desiredClass,
  625.                                                                 const FW_CDesc& selectionData)
  626. {
  627.     FW_MScriptable* requestedObject = NULL;
  628.     ODDescType        specifierType = selectionData.DescriptorType();
  629.     
  630.     if (specifierType == typeAbsoluteOrdinal)
  631.     {
  632.         switch (selectionData.GetAbsoluteOrdinal())
  633.         {
  634.             case kAEFirst:
  635.                 requestedObject = AcquireFirstElement(ev, part, desiredClass);
  636.                 break;
  637.             
  638.             case kAEMiddle:
  639.                 requestedObject = AcquireMiddleElement(ev, part, desiredClass);
  640.                 break;
  641.             
  642.             case kAELast:
  643.                 requestedObject = AcquireLastElement(ev, part, desiredClass);
  644.                 break;
  645.                 
  646.             case kAEAny:
  647.                 requestedObject = AcquireAnyElement(ev, part, desiredClass);
  648.                 break;
  649.                 
  650.             case kAEAll:
  651.                 requestedObject = AcquireAllElements(ev, part, desiredClass);
  652.                 break;
  653.                 
  654.             default:
  655.                 break;
  656.         }
  657.         
  658.     }
  659.     else if (specifierType == typeLongInteger)
  660.     {
  661.         long objectIndex;
  662.         selectionData >> objectIndex;
  663.         
  664.         if (objectIndex < 0)
  665.             objectIndex += (CountElements(ev, part, desiredClass) + 1);
  666.             
  667.         requestedObject = AcquireElementByIndex(ev, part, desiredClass, objectIndex);
  668.     }
  669.     
  670.     return requestedObject;
  671. }
  672.  
  673. //---------------------------------------------------------------------------------------
  674. // FW_MScriptable::AcquireElementByName: default implementation iterates through
  675. // contained elements of the specified type looking for a name match. Subclasses
  676. // may be able to optimize searching based on knowledge of content.
  677. //---------------------------------------------------------------------------------------
  678.  
  679. FW_MScriptable* FW_MScriptable::AcquireElementByName(Environment* ev,
  680.                                                     FW_CPart* part,
  681.                                                     ODDescType desiredClass,
  682.                                                     const FW_CString& desiredName)
  683. {
  684.     FW_CElementIterator* iter = NewElementIterator(ev, part, desiredClass);
  685.     
  686.     FW_VOLATILE(iter);
  687.     
  688.     FW_CDesc nameDesc;
  689.     FW_CString nameString;
  690.     FW_MScriptable* desiredObject = NULL;
  691.     
  692.     FW_TRY
  693.     {
  694.         for (FW_MScriptable* currentObject = iter->First(); 
  695.                 iter->IsNotComplete() && !desiredObject; currentObject = iter->Next())
  696.         {
  697.             if (currentObject->HasProperty(pName))
  698.             {
  699.                 currentObject->GetProperty(ev, part, nameDesc, pName, typeChar);
  700.                 nameDesc.GetString(nameString);
  701.                 
  702.                 if (desiredName == nameString)
  703.                     desiredObject = currentObject;
  704.                 else
  705.                     nameDesc.Clear();
  706.             }
  707.         }
  708.     }
  709.     FW_CATCH_BEGIN
  710.     FW_CATCH_EVERYTHING()
  711.     {
  712.         delete iter;
  713.         FW_THROW_SAME();
  714.     }
  715.     FW_CATCH_END
  716.     
  717.     delete iter;
  718.     
  719.     if (desiredObject)
  720.         desiredObject->AcquireScriptable();
  721.     return desiredObject;
  722. }
  723.  
  724.  
  725. //---------------------------------------------------------------------------------------
  726. //    FW_MScriptable::CountElements
  727. //---------------------------------------------------------------------------------------
  728.  
  729. long FW_MScriptable::CountElements(Environment* ev,
  730.                                     FW_CPart* part,
  731.                                     ODDescType desiredClass)
  732. {
  733.     unsigned long count = 0;
  734.     FW_CElementIterator* iter = NewElementIterator(ev, part, desiredClass);
  735.     FW_VOLATILE(iter);
  736.     
  737.     FW_TRY
  738.     {
  739.         for (iter->First(); iter->IsNotComplete(); iter->Next())
  740.             count++;
  741.     }
  742.     FW_CATCH_BEGIN
  743.     FW_CATCH_EVERYTHING()
  744.     {
  745.         delete iter;
  746.         FW_THROW_SAME();
  747.     }
  748.     FW_CATCH_END
  749.     
  750.     delete iter;
  751.     
  752.     return count;
  753. }
  754.  
  755. //---------------------------------------------------------------------------------------
  756. //    FW_MScriptable::AcquireElementByIndex
  757. //---------------------------------------------------------------------------------------
  758.  
  759. FW_MScriptable* FW_MScriptable::AcquireElementByIndex(Environment* ev,
  760.                                                 FW_CPart* part,
  761.                                                 ODDescType desiredClass, 
  762.                                                 long index)
  763. {
  764.     FW_MScriptable* desiredObject = NULL;
  765.     FW_CElementIterator* iter = NewElementIterator(ev, part, desiredClass);
  766.     FW_VOLATILE(iter);
  767.     
  768.     FW_TRY
  769.     {
  770.         long count = 0;
  771.         
  772.         for (FW_MScriptable* currentObject = iter->First(); count <= index && iter->IsNotComplete();
  773.             currentObject = iter->Next())
  774.         {
  775.             if (++count == index)
  776.                 desiredObject = currentObject;
  777.         }
  778.     }
  779.     FW_CATCH_BEGIN
  780.     FW_CATCH_EVERYTHING()
  781.     {
  782.         delete iter;
  783.         FW_THROW_SAME();
  784.     }
  785.     FW_CATCH_END
  786.     
  787.     delete iter;
  788.     
  789.     if (desiredObject)
  790.         desiredObject->AcquireScriptable();
  791.     return desiredObject;
  792. }
  793.  
  794. //---------------------------------------------------------------------------------------
  795. //    FW_MScriptable::AcquireFirstElement
  796. //---------------------------------------------------------------------------------------
  797.  
  798. FW_MScriptable* FW_MScriptable::AcquireFirstElement(Environment* ev,
  799.                                                 FW_CPart* part,
  800.                                                 ODDescType desiredClass)
  801. {
  802.     return (AcquireElementByIndex(ev, part, desiredClass, 1));
  803. }
  804.  
  805. //---------------------------------------------------------------------------------------
  806. //    FW_MScriptable::AcquireMiddleElement
  807. //---------------------------------------------------------------------------------------
  808.  
  809. FW_MScriptable* FW_MScriptable::AcquireMiddleElement(Environment* ev,
  810.                                                 FW_CPart* part,
  811.                                                 ODDescType desiredClass)
  812. {
  813.     return (AcquireElementByIndex(ev, part, desiredClass, (CountElements(ev, part, desiredClass) + 1) / 2));
  814. }
  815.  
  816. //---------------------------------------------------------------------------------------
  817. //    FW_MScriptable::AcquireLastElement
  818. //---------------------------------------------------------------------------------------
  819.  
  820. FW_MScriptable* FW_MScriptable::AcquireLastElement(Environment* ev,
  821.                                             FW_CPart* part,
  822.                                             ODDescType desiredClass)
  823. {
  824.     return (AcquireElementByIndex(ev, part, desiredClass, CountElements(ev, part, desiredClass)));
  825. }
  826.  
  827. //---------------------------------------------------------------------------------------
  828. //    FW_MScriptable::AcquireAnyElement
  829. //---------------------------------------------------------------------------------------
  830.  
  831. FW_MScriptable* FW_MScriptable::AcquireAnyElement(Environment* ev,
  832.                                             FW_CPart* part,
  833.                                             ODDescType desiredClass)
  834. {
  835. FW_UNUSED(ev);
  836. FW_UNUSED(part);
  837. FW_UNUSED(desiredClass);
  838.     FW_PRIV_ASSERT(Not_Yet_Implemented);
  839.     return NULL;
  840. }
  841.  
  842. //---------------------------------------------------------------------------------------
  843. //    FW_MScriptable::AcquireAllElements
  844. //---------------------------------------------------------------------------------------
  845.  
  846. FW_MScriptable* FW_MScriptable::AcquireAllElements(Environment* ev,
  847.                                             FW_CPart* part,
  848.                                             ODDescType desiredClass)
  849. {
  850.     FW_CElementIterator* iter = NULL;
  851.     FW_VOLATILE(iter);
  852.     FW_CAcquiredScriptableCollection collection;
  853.     FW_VOLATILE(collection);
  854.     
  855.     FW_TRY
  856.     {
  857.         iter = NewElementIterator(ev, part, desiredClass);
  858.         collection = FW_NEW(FW_CScriptableCollection, ());
  859.         
  860.         for (FW_MScriptable* currentObject = iter->First(); iter->IsNotComplete();
  861.             currentObject = iter->Next())
  862.         {
  863.             collection->Add(currentObject);
  864.         }
  865.         delete iter;
  866.     }
  867.     FW_CATCH_BEGIN
  868.     FW_CATCH_EVERYTHING()
  869.     {
  870.         delete iter;
  871.         
  872.         FW_THROW_SAME();
  873.     }
  874.     FW_CATCH_END
  875.             
  876.     if (collection->Count() == 0)
  877.     {
  878.         return NULL;
  879.     }
  880.     else
  881.     {
  882.         collection->AcquireScriptable();
  883.         return collection;
  884.     }
  885. }
  886.  
  887. //---------------------------------------------------------------------------------------
  888. //    FW_MScriptable::AcquireAdjacentObject
  889. //---------------------------------------------------------------------------------------
  890.  
  891. FW_MScriptable* FW_MScriptable::AcquireAdjacentObject(Environment* ev,
  892.                                                 FW_CPart* part,
  893.                                                 ODDescType desiredClass,
  894.                                                 ODDescType relativePosition) const
  895. {
  896.     FW_MScriptable* result = NULL;
  897.     FW_MScriptable* container = AcquireContainingObject(ev, part);
  898.     
  899.     if (container)
  900.     {
  901.         FW_CElementIterator* iter = container->NewElementIterator(ev, part, desiredClass);
  902.         FW_VOLATILE(iter);
  903.         
  904.         FW_MScriptable* previous = NULL;
  905.         FW_Boolean            keepGoing = TRUE;
  906.         FW_Boolean            fetchNext = FALSE;
  907.         
  908.         FW_TRY
  909.         {
  910.             for (FW_MScriptable* currentObject = iter->First(); keepGoing && iter->IsNotComplete();
  911.                 currentObject = iter->Next())
  912.             {
  913.                 if (fetchNext)
  914.                 {
  915.                     result = currentObject;
  916.                     keepGoing = FALSE;
  917.                 }
  918.                 else if (currentObject == this)
  919.                 {
  920.                     if (relativePosition == kAEPrevious)
  921.                     {
  922.                         result = previous;
  923.                         keepGoing = FALSE;
  924.                     }
  925.                     else
  926.                         fetchNext = TRUE;
  927.                 }
  928.                 previous = currentObject;
  929.             }
  930.         }
  931.         FW_CATCH_BEGIN
  932.         FW_CATCH_EVERYTHING()
  933.         {
  934.             delete iter;
  935.             FW_THROW_SAME();
  936.         }
  937.         FW_CATCH_END
  938.     }
  939.     
  940.     if (result)
  941.         result->AcquireScriptable();
  942.     return result;
  943. }
  944.  
  945. //---------------------------------------------------------------------------------------
  946. //    FW_MScriptable::AcquireElementsWithinRange
  947. //---------------------------------------------------------------------------------------
  948.  
  949. FW_MScriptable* FW_MScriptable::AcquireElementsWithinRange(Environment* ev,
  950.                                                     FW_CPart* part,
  951.                                                     ODDescType desiredClass,
  952.                                                     FW_MScriptable* startObject,
  953.                                                     FW_MScriptable* stopObject) const
  954. {
  955.     FW_CElementIterator* iter = NewElementIterator(ev, part, desiredClass);
  956.     FW_CAcquiredScriptableCollection collection = FW_NEW(FW_CScriptableCollection, ());
  957.     
  958.     FW_Boolean foundStart = FALSE;
  959.     FW_Boolean foundStop = FALSE;
  960.     
  961.     FW_CAcquiredScriptable acquiredScriptable;
  962.     
  963.     for (FW_MScriptable* currentObject = iter->First(); !foundStop && iter->IsNotComplete();
  964.         currentObject = iter->Next())
  965.     {
  966.         FW_CDesc objectDesc;
  967.         
  968.         ::FW_InsertScriptableIntoDesc(currentObject, objectDesc);
  969.         acquiredScriptable = currentObject;    // balances acquire/release
  970.         
  971.         if (!foundStart)
  972.             foundStart = startObject->CompareScriptableObjects(ev, part, kAEEquals, objectDesc);
  973.         
  974.         if (foundStart)
  975.             collection->Add(currentObject);
  976.         
  977.         foundStop = stopObject->CompareScriptableObjects(ev, part, kAEEquals, objectDesc);
  978.     }
  979.     
  980.     collection->AcquireScriptable();
  981.     return collection;
  982. }
  983.  
  984. //---------------------------------------------------------------------------------------
  985. //    FW_MScriptable::NewElementIterator
  986. //---------------------------------------------------------------------------------------
  987.  
  988. FW_CElementIterator* FW_MScriptable::NewElementIterator(Environment* ev,
  989.                                                         FW_CPart* part,
  990.                                                         ODDescType desiredClass) const
  991. {
  992. FW_UNUSED(ev);
  993. FW_UNUSED(part);
  994. FW_UNUSED(desiredClass);
  995.     FW_Failure(errAEEventNotHandled);
  996.     return NULL;
  997. }
  998.  
  999. //---------------------------------------------------------------------------------------
  1000. //    FW_MScriptable::HasProperty
  1001. //---------------------------------------------------------------------------------------
  1002.  
  1003. FW_Boolean FW_MScriptable::HasProperty(ODDescType whichProperty) const
  1004. {
  1005.     return (whichProperty == pClass);    // class is the only supported property
  1006. }
  1007.  
  1008. //---------------------------------------------------------------------------------------
  1009. //    FW_MScriptable::BuildObjectSpecifier
  1010. //---------------------------------------------------------------------------------------
  1011.  
  1012. void FW_MScriptable::BuildObjectSpecifier(Environment* ev,
  1013.                                         FW_CPart* part,
  1014.                                         const FW_CFrame* frame,
  1015.                                         FW_CDesc& specifier,
  1016.                                         ODDescType preferredForm) const
  1017. {
  1018.     FW_MScriptable* container = AcquireContainingObject(ev, part);
  1019.     
  1020.     FW_CDesc             containerSpecifier;
  1021.     FW_CDesc            mySpecifier;
  1022.     FW_Boolean            gotData = FALSE;
  1023.     
  1024.     container->BuildObjectSpecifier(ev, part, frame, containerSpecifier, container->GetSpecifierForm());
  1025.     
  1026.     switch (preferredForm)
  1027.     {
  1028.         case formName:
  1029.             gotData = HasProperty(pName) && GetProperty(ev, part, mySpecifier, pName);
  1030.             break;
  1031.             
  1032.         case formUniqueID:
  1033.             gotData  = HasProperty(pID) && GetProperty(ev, part, mySpecifier, pID);
  1034.             break;
  1035.             
  1036.         case formAbsolutePosition:
  1037.             gotData = HasProperty(pIndex) && GetProperty(ev, part, mySpecifier, pIndex);
  1038.             break;
  1039.             
  1040.         default:
  1041.             break;
  1042.     }
  1043.     
  1044.     if (!gotData)
  1045.         FW_Failure(errAECantSupplyType);
  1046.  
  1047.     ::FW_CreateObjSpecifier(GetObjectClass(), containerSpecifier, preferredForm, mySpecifier, specifier);
  1048. }
  1049.  
  1050. //---------------------------------------------------------------------------------------
  1051. //    FW_MScriptable::GetObjectSpecifier
  1052. //---------------------------------------------------------------------------------------
  1053.  
  1054. void FW_MScriptable::GetObjectSpecifier(Environment* ev,
  1055.                                         FW_CPart* part,
  1056.                                         FW_CDesc& specifier) const
  1057. {
  1058.     BuildObjectSpecifier(ev, part, GetFrame(ev, part), specifier, GetSpecifierForm());
  1059. }
  1060.  
  1061. //---------------------------------------------------------------------------------------
  1062. //    FW_MScriptable::GetPropertySpecifier
  1063. //---------------------------------------------------------------------------------------
  1064.  
  1065. void FW_MScriptable::GetPropertySpecifier(Environment* ev,
  1066.                                         FW_CPart* part,
  1067.                                         ODDescType whichProperty,
  1068.                                         FW_CDesc& specifier)
  1069. {
  1070.     if (HasProperty(whichProperty))
  1071.     {
  1072.         FW_CDesc     objectDesc;
  1073.         FW_CDesc    propertyDesc;
  1074.         
  1075.         GetObjectSpecifier(ev, part, objectDesc);
  1076.         propertyDesc.PutType(whichProperty);
  1077.         
  1078.         ::FW_CreateObjSpecifier(cProperty, objectDesc, formPropertyID, propertyDesc, specifier);
  1079.     }
  1080.     else
  1081.         FW_Failure(errAENoSuchObject);
  1082. }
  1083.  
  1084. //---------------------------------------------------------------------------------------
  1085. //    FW_MScriptable::GetPropertyInfo
  1086. //---------------------------------------------------------------------------------------
  1087.  
  1088. void FW_MScriptable::GetPropertyInfo(Environment* ev,
  1089.                                     FW_CPart* part,
  1090.                                     FW_Boolean& canUndo,
  1091.                                     FW_Boolean& causesChange) const
  1092. {
  1093. FW_UNUSED(ev);
  1094. FW_UNUSED(part);
  1095.     canUndo = TRUE;
  1096.     causesChange = TRUE;
  1097. }
  1098.  
  1099. //---------------------------------------------------------------------------------------
  1100. //    FW_MScriptable::GetProperty
  1101. //---------------------------------------------------------------------------------------
  1102.  
  1103. FW_Boolean FW_MScriptable::GetProperty(Environment* ev, 
  1104.                                     FW_CPart* part,
  1105.                                     FW_CDesc& propertyValue, 
  1106.                                     ODDescType whichProperty, 
  1107.                                     ODDescType desiredClass) const
  1108. {
  1109. FW_UNUSED(desiredClass);
  1110.     FW_Boolean hasProperty = FALSE;
  1111.     
  1112.     switch (whichProperty)
  1113.     {
  1114.         case pClass:
  1115.             {
  1116.                 ODDescType itsClass = GetObjectClass();
  1117.                 propertyValue << itsClass;
  1118.                 hasProperty = TRUE;
  1119.             }
  1120.             break;
  1121.         
  1122.         case pIndex:
  1123.             {
  1124.                 FW_MScriptable* container = AcquireContainingObject(ev, part);
  1125.                 FW_CElementIterator* iter = container->NewElementIterator(ev, part, GetObjectClass());
  1126.                 FW_VOLATILE(iter);
  1127.                 
  1128.                 long     index = 1;
  1129.                 
  1130.                 FW_TRY
  1131.                 {
  1132.                     for (FW_MScriptable* semObj = iter->First(); iter->IsNotComplete() && !hasProperty; semObj = iter->Next(), index++)
  1133.                     {
  1134.                         if (semObj == this)
  1135.                         {
  1136.                             propertyValue << index;
  1137.                             hasProperty = TRUE;
  1138.                         }
  1139.                     }
  1140.                 }
  1141.                 FW_CATCH_BEGIN
  1142.                 FW_CATCH_EVERYTHING()
  1143.                 {
  1144.                     delete iter;
  1145.                     FW_THROW_SAME();
  1146.                 }
  1147.                 FW_CATCH_END
  1148.             }
  1149.             break;
  1150.             
  1151.         default:
  1152.             hasProperty = FALSE;
  1153.             break;    
  1154.     }
  1155.     
  1156.     return hasProperty;
  1157. }
  1158.  
  1159. //---------------------------------------------------------------------------------------
  1160. //    FW_MScriptable::SaveProperty
  1161. //---------------------------------------------------------------------------------------
  1162.  
  1163. void FW_MScriptable::SaveProperty(Environment* ev,
  1164.                                 FW_CPart* part,
  1165.                                 FW_CDesc& propertyValue,
  1166.                                 ODDescType whichProperty,
  1167.                                 ODDescType desiredClass) const
  1168. {
  1169.     if (!GetProperty(ev, part, propertyValue, whichProperty, desiredClass))
  1170.         FW_Failure(errAEEventNotHandled);
  1171. }
  1172.  
  1173. //---------------------------------------------------------------------------------------
  1174. //    FW_MScriptable::SetProperty
  1175. //---------------------------------------------------------------------------------------
  1176.  
  1177. void FW_MScriptable::SetProperty(Environment* ev, 
  1178.                                 FW_CPart* part, 
  1179.                                 FW_CDesc& propertyValue, 
  1180.                                 ODDescType whichProperty)
  1181. {
  1182.         // scriptable objects that support setting the "contents" property
  1183.         // should test for cProperty in HasProperty and return true
  1184.     if (whichProperty == cProperty)
  1185.     {
  1186.         SetProperties(ev, part, propertyValue);
  1187.     }
  1188.     else
  1189.         FW_Failure(errAEEventNotHandled);
  1190. }
  1191.  
  1192. //---------------------------------------------------------------------------------------
  1193. //    FW_MScriptable::SetProperties
  1194. //---------------------------------------------------------------------------------------
  1195.  
  1196. void FW_MScriptable::SetProperties(Environment* ev,
  1197.                                 FW_CPart* part,
  1198.                                 const FW_CDesc& contents)
  1199. {
  1200.     if (contents.IsRecord())
  1201.     {
  1202.         FW_CDesc value;
  1203.         long propertyCount = contents.GetItemCount();
  1204.         for (long index = 1; index <= propertyCount; index++)
  1205.         {
  1206.             ODDescType whichProperty;
  1207.             value.Clear();
  1208.             contents.GetDescFromList(index, whichProperty, value);
  1209.             SetProperty(ev, part, value, whichProperty);
  1210.         }
  1211.     }
  1212.     else
  1213.         FW_Failure(errAEEventNotHandled);
  1214. }
  1215.  
  1216. //---------------------------------------------------------------------------------------
  1217. //    FW_MScriptable::SetProperties
  1218. //---------------------------------------------------------------------------------------
  1219.  
  1220. void FW_MScriptable::SetProperties(Environment* ev,
  1221.                                 FW_CPart* part,
  1222.                                 const FW_CAppleEvent& event)
  1223. {
  1224.     
  1225.     if (event.HasDataKey(keyAEPropData))
  1226.     {
  1227.         FW_CDesc propertyList;
  1228.         
  1229.         event.GetDataByDesc(propertyList, keyAEPropData, typeAERecord);
  1230.         SetProperties(ev, part, propertyList);
  1231.     }
  1232. }
  1233.  
  1234. //---------------------------------------------------------------------------------------
  1235. //    FW_MScriptable::RestoreProperty
  1236. //---------------------------------------------------------------------------------------
  1237.  
  1238. void FW_MScriptable::RestoreProperty(Environment* ev,
  1239.                                     FW_CPart* part,
  1240.                                     FW_CDesc& propertyValue,
  1241.                                     ODDescType whichProperty)
  1242. {
  1243.     this->SetProperty(ev, part, propertyValue, whichProperty);
  1244. }
  1245.                                         
  1246. //---------------------------------------------------------------------------------------
  1247. //    FW_MScriptable::GetUndoSetPropertyStrings
  1248. //---------------------------------------------------------------------------------------
  1249.  
  1250. void FW_MScriptable::GetUndoStrings(Environment* ev,
  1251.                                     FW_CPart* part,
  1252.                                     ODDescType whichProperty,
  1253.                                     FW_CString& undoString,
  1254.                                     FW_CString& redoString) const
  1255. {
  1256. FW_UNUSED(part);
  1257. FW_UNUSED(whichProperty);
  1258.         // "Undo Set Property" and "Redo Set Property"
  1259.         // Subclasses can optionally override and provide more descriptive strings
  1260.     ::FW_PrivLoadUndoStrings(ev, FW_kUndoSetPropertyMsg, undoString, redoString);
  1261. }
  1262.  
  1263. //---------------------------------------------------------------------------------------
  1264. //    FW_MScriptable::AddDependent
  1265. //---------------------------------------------------------------------------------------
  1266.  
  1267. void FW_MScriptable::AddDependent(FW_MScriptable* dependent)
  1268. {
  1269.     if (!fDependents)
  1270.         fDependents = FW_NEW(FW_TOrderedCollection<FW_MScriptable>, ());
  1271.     fDependents->AddFirst(dependent);
  1272. }
  1273.  
  1274. //---------------------------------------------------------------------------------------
  1275. //    FW_MScriptable::RemoveDependent
  1276. //---------------------------------------------------------------------------------------
  1277.  
  1278. void FW_MScriptable::RemoveDependent(FW_MScriptable* dependent)
  1279. {
  1280.     FW_ASSERT(fDependents);
  1281.     fDependents->Remove(dependent);
  1282. }
  1283.  
  1284. //---------------------------------------------------------------------------------------
  1285. //    FW_MScriptable::HandlePrimaryDeleted
  1286. //---------------------------------------------------------------------------------------
  1287.  
  1288. void FW_MScriptable::HandlePrimaryDeleted(FW_MScriptable* primary)
  1289. {
  1290. FW_UNUSED(primary);
  1291.     FW_DEBUG_MESSAGE("FW_MScriptable::HandlePrimaryDeleted should be handled by a derived class");
  1292. }
  1293.  
  1294. //========================================================================================
  1295. //    class FW_CElementIterator
  1296. //========================================================================================
  1297.  
  1298. //---------------------------------------------------------------------------------------
  1299. //    FW_CElementIterator::FW_CElementIterator
  1300. //---------------------------------------------------------------------------------------
  1301.  
  1302. FW_CElementIterator::FW_CElementIterator()
  1303. {
  1304.     FW_END_CONSTRUCTOR
  1305. }
  1306.  
  1307. //---------------------------------------------------------------------------------------
  1308. //    FW_CElementIterator::~FW_CElementIterator
  1309. //---------------------------------------------------------------------------------------
  1310.  
  1311. FW_CElementIterator::~FW_CElementIterator()
  1312. {
  1313.     FW_START_DESTRUCTOR
  1314. }
  1315.